#include "BaseType.h"
#include "Tracer.h"

using namespace libemb;

/**
 * 建造者模式(生成器模式)：
 * 1.抽象建造者定义了建造产品各组件的接口
 * 2.具体建造者提供建造产品各组件的方法，并最后将其组装成产品。
 * 3.建造组件的顺序不一样，组装出来的产品可能也不一样。
 * 适用场景：
 * 1.创建复杂对象的方法独立于该对象的组成部分以及它的组装方法。
 */

//角色建造器
class RoleBuilder{
public:
    virtual void buildAge()=0;
    virtual void buildName()=0;
protected:
    std::string m_roleInfo;
};  

//Jack建造器
class JackBuilder:public RoleBuilder{
DECL_CLASSNAME(JackBuilder)
public:
    void buildAge()override
    {
        m_roleInfo += "He is 25 year old; ";
    }
    void buildName()override
    {
        m_roleInfo += "His name is Jack; ";
    }
    void getRole()
    {
        TRACE_DBG_CLASS("Role info: %s",CSTR(m_roleInfo));
    }
};

//Lucy建造器
class LucyBuilder:public RoleBuilder{
DECL_CLASSNAME(LucyBuilder)
public:
    void buildAge()override
    {
        m_roleInfo += "She is 23 year old; ";
    }
    void buildName()override
    {
        m_roleInfo += "Her name is Lucy; ";
    }
    void getRole()
    {
        TRACE_DBG_CLASS("Role info: %s",CSTR(m_roleInfo));
    }
};

//导演
class Director{
public:
    void buildRole()
    {
        m_jack = std::make_shared<JackBuilder>();
        m_jack->buildAge();
        m_jack->buildName();
        
        m_lucy = std::make_shared<LucyBuilder>();
        m_lucy->buildName();
        m_lucy->buildAge();
        
    }

    void play()
    {
        m_jack->getRole();
        m_lucy->getRole();
    }

private:
    std::shared_ptr<JackBuilder> m_jack{nullptr};
    std::shared_ptr<LucyBuilder> m_lucy{nullptr};
};

int main()
{
    Tracer::getInstance().setLevel(TRACE_LEVEL_DBG);
	Tracer::getInstance().addSink(std::make_shared<STDSink>()).start();

    Director director;
    director.buildRole();
    director.play();
    return RC_OK;
}